home *** CD-ROM | disk | FTP | other *** search
/ Pascal Super Library / Pascal Super Library (CW International)(1997).bin / PGM_TOOL / RLINE_OP / MOVEOPS.PAS next >
Pascal/Delphi Source File  |  1989-10-10  |  8KB  |  363 lines

  1. {$A+,B-,D+,E-,F-,I-,L+,N-,O-,R-,S-,V-}
  2. {$M 16384,0,655360}
  3. UNIT MoveOps;
  4.  
  5. { Objects to move around in a rectangle. }
  6.  
  7. (***************************************)
  8. INTERFACE
  9. (***************************************)
  10.  
  11. USES
  12.   CRT, DOS;
  13.  
  14. TYPE
  15.   Str80 = string[80];
  16.  
  17.   Rectangle = Object
  18.         x1,y1,x2,y2 : integer;
  19.         Height,Width : Integer;
  20.         PROCEDURE Init(px1,py1,px2,py2 : integer);
  21.           END;
  22.  
  23.   ScreenR = object(Rectangle)
  24.         IxNoY1 : LongInt;
  25.         TotalItems : LongInt;     { Total number of items. }
  26.         FirstColumn : Integer;    { First column displayed. }
  27.         Constructor Init(px1,py1,px2,py2 : integer;
  28.                    TotItems : LongInt);
  29.         FUNCTION DTAline(Row : LongInt) : String; virtual;
  30.         { Returns string at Row }
  31.         PROCEDURE WrScrLn(Y : Integer); virtual;
  32.         { Write the proper string at SCREEN line Y }
  33.         PROCEDURE PgUp;
  34.         PROCEDURE PgDn;
  35.         PROCEDURE TOFL;
  36.         PROCEDURE EOFL;  virtual;
  37.         PROCEDURE ScrollUp;
  38.         PROCEDURE ScrollDown;
  39.         PROCEDURE MoveLeft(i : Integer);
  40.         PROCEDURE MoveRight(i : Integer);
  41.         PROCEDURE WrScr;   { writes entire screen. }
  42.         PROCEDURE GotoLine(X : LongInt);
  43.         Destructor Done;
  44.           END;
  45.  
  46.   Scroller = object(ScreenR)
  47.         SearchString : string[80];
  48.         CaseSensitive : Boolean;
  49.         Constructor Init(px1,py1,px2,py2 : integer;
  50.                    TotItems : LongInt);
  51.         PROCEDURE ShowStatus; virtual;
  52.         PROCEDURE Help; virtual;
  53.         PROCEDURE AutoScroll;
  54.         FUNCTION ScrollSelect : Char; virtual;
  55.         FUNCTION AskString(prompt : string) : string; virtual;
  56.         PROCEDURE Message(s : str80); Virtual;
  57.         PROCEDURE SearchForward; virtual;
  58.           END;
  59.  
  60.   PROCEDURE UpCaseString(var s : string);
  61.   FUNCTION InsensitiveMatch(var s1,s2 : string) : boolean;
  62.  
  63.  
  64. (*****************************************************)
  65. implementation
  66. (*****************************************************)
  67.  
  68. {-------- Rectangle -------------}
  69.  
  70.   PROCEDURE Rectangle.Init(px1,py1,px2,py2 : integer);
  71.   BEGIN
  72.     x1 := px1;
  73.     y1 := py1;
  74.     x2 := px2;
  75.     y2 := py2;
  76.     height := y2-y1+1;
  77.     width := x2-x1+1;
  78.   END;
  79.  
  80.   Constructor ScreenR.Init(px1,py1,px2,py2 : integer;
  81.             TotItems : LongInt);
  82.   BEGIN
  83.     Rectangle.Init(px1,py1,px2,py2);
  84.     TotalItems := TotItems;
  85.     IxNoY1 := 1;
  86.     FirstColumn := 1;
  87.   END;
  88.  
  89.   Destructor ScreenR.Done;  BEGIN  END;
  90.  
  91.   FUNCTION ScreenR.DTAline(Row : LongInt) : String;
  92.   { responsible for returning line at 'Row'.  }
  93.   { If Row < 1 or > TotalItems, returns '' blank string. }
  94.   BEGIN
  95.     runerror(211);
  96.   END;
  97.  
  98.   PROCEDURE ScreenR.WrScrLn(Y : Integer);
  99.   VAR
  100.     s : string;
  101.   BEGIN              { WrScrLn }
  102.     s := DTALine(Pred(Y + IxnoY1));
  103.     s := copy(s, FirstColumn, width);
  104.     if length(s) < width then BEGIN
  105.       fillchar(s[length(s)+1], width-length(s), ' ');
  106.       s[0] := char(width);
  107.     END;
  108.     gotoxy(x1, pred(Y+y1));
  109.     if wherey = 25
  110.     then dec(s[0]);     { avoid scrolling the window writing at last column }
  111.     write(s)
  112.   END;
  113.  
  114.   PROCEDURE ScreenR.WrScr;
  115.   VAR
  116.     cy        : Integer;
  117.   BEGIN
  118.     FOR cy := 1 TO Height
  119.     DO WrScrLn(cy);
  120.   END;
  121.  
  122.   PROCEDURE ScreenR.ScrollUp;
  123.   var
  124.    r : registers;
  125.   BEGIN
  126.     IF Pred(IxNoY1+Height) < TotalItems THEN BEGIN
  127.       Inc(IxNoY1);
  128.       IF Height > 1 then with r do BEGIN
  129.     ax := $0601;  { scroll window, 1 line. }
  130.     bh := textattr;
  131.     ch := pred(y1);
  132.     cl := pred(x1);
  133.     dh := pred(y2);
  134.     dl := pred(x2);
  135.     intr($10,r);
  136.       END;
  137.       WrScrLn(Height);
  138.     END;
  139.   END;
  140.  
  141.   PROCEDURE ScreenR.ScrollDown;
  142.   var
  143.     r : registers;
  144.   BEGIN
  145.     IF IxNoY1 <> 1 THEN BEGIN
  146.       Dec(IxNoY1);
  147.       IF Height > 1 then with r do BEGIN
  148.     ax := $0701;  { scroll window, 1 line. }
  149.     bh := textattr;
  150.     ch := pred(y1);
  151.     cl := pred(x1);
  152.     dh := pred(y2);
  153.     dl := pred(x2);
  154.     intr($10,r);
  155.       END;
  156.       WrScrLn(1);
  157.     END;
  158.   END;
  159.  
  160.   PROCEDURE ScreenR.MoveLeft(i : Integer);
  161.   BEGIN
  162.     Dec(FirstColumn,i);
  163.     If FirstColumn < 1
  164.     Then FirstColumn := 1;
  165.     WrScr;
  166.   END;
  167.  
  168.   PROCEDURE ScreenR.MoveRight(i : Integer);
  169.   BEGIN
  170.     Inc(FirstColumn,i);
  171.     If FirstColumn > 255-width
  172.     Then Firstcolumn := 255-width;
  173.     WrScr;
  174.   END;
  175.  
  176.   PROCEDURE ScreenR.TOFL;         { ^A }
  177.   BEGIN
  178.     IxNoY1 := 1;
  179.     FirstColumn := 1;
  180.     WrScr;
  181.   END;
  182.  
  183.   PROCEDURE ScreenR.EoFL;
  184.   BEGIN
  185.     IF TotalItems >= Height
  186.     THEN IxnoY1 := Succ(TotalItems-Height)
  187.     ELSE IxnoY1 := 1;
  188.     WrScr;
  189.   END;
  190.  
  191.   PROCEDURE ScreenR.PgUp;
  192.   BEGIN         { PgUp }
  193.     IF IxNoY1 > Height
  194.     THEN Dec(IxNoY1, Height)
  195.     ELSE IxnoY1 := 1;
  196.     WrScr;
  197.   END;
  198.  
  199.   PROCEDURE ScreenR.PgDn;
  200.   BEGIN         { PgDn }
  201.     IF Pred(IxNoY1)+(Height*2) <= Pred(TotalItems) THEN BEGIN
  202.       Inc(IxNoY1, Height);
  203.       WrScr;
  204.     END ELSE EOFl;
  205.   END;
  206.  
  207.   PROCEDURE ScreenR.GotoLine(X : LongInt);
  208.   BEGIN
  209.     IxnoY1 := X;
  210.     wrscr;
  211.   END;
  212.  
  213. { SCROLLER ------------------------------------------------------}
  214.  
  215.   Constructor Scroller.Init(px1,py1,px2,py2 : integer;
  216.             TotItems : LongInt);
  217.   BEGIN
  218.     ScreenR.Init(px1,py1,px2,py2,TotItems);
  219.     SearchString := '';
  220.     CaseSensitive := false;
  221.   END;
  222.  
  223.   FUNCTION Scroller.AskString(prompt : string) : string;
  224.   BEGIN
  225.     AskString := '';
  226.   END;
  227.  
  228.   PROCEDURE Scroller.ShowStatus;  BEGIN END;
  229.   PROCEDURE Scroller.Message(s : Str80); BEGIN END;
  230.   PROCEDURE Scroller.Help;  BEGIN END;
  231.  
  232.   PROCEDURE UpCaseString(var s : string);
  233.   var
  234.     i : integer;
  235.   BEGIN
  236.     for i := 1 to length(s) do s[i] := upcase(s[i]);
  237.   END;
  238.  
  239.   FUNCTION InsensitiveMatch(var s1,s2 : string) : boolean;
  240.   { s1 should be upper cased. }
  241.   var
  242.     i, j, k : integer;
  243.     len : integer;
  244.   BEGIN
  245.     i := pos(s1[1],s2);
  246.     j := pos(chr(ord(s1[1])+32), s2);
  247.     IF (i or j) <> 0 THEN BEGIN
  248.       if ((i > 0) and (i < j)) or (j = 0)
  249.       then j := i;
  250.       for i := j to length(s2)-length(s1)+1 do
  251.     if upcase(s2[i]) = s1[1] then BEGIN
  252.       j := 2;
  253.       k := succ(i);
  254.       while (j <= length(s1)) and (s1[j] = upcase(s2[k])) do BEGIN
  255.         inc(k);
  256.         inc(j);
  257.       END;
  258.       if j > length(s1) then BEGIN
  259.         InsensitiveMatch := true;
  260.         Exit;
  261.       END;
  262.     END;
  263.     END;
  264.     InsensitiveMatch := false;
  265.   END;
  266.  
  267.   PROCEDURE Scroller.SearchForward;
  268.   var
  269.    i : longint;
  270.    s2 : string;
  271.    j,k : integer;
  272.   BEGIN
  273.     if length(SearchString) = 0 then Exit;
  274.     Message('Searching forward for "'+searchstring+'"');
  275.     if not casesensitive then BEGIN
  276.       for i := IxnoY1+1 to totalitems do BEGIN
  277.     s2 := dtaline(i);
  278.     if InsensitiveMatch(SearchString,s2) then BEGIN
  279.       GotoLine(i);
  280.       Exit;
  281.     END;
  282.       END;
  283.     END ELSE BEGIN { case sensitive }
  284.       for i := Ixnoy1+1 to totalitems do BEGIN
  285.     if pos(SearchString,dtaline(i)) <> 0 then BEGIN
  286.       GotoLine(i);
  287.       Exit;
  288.     END;
  289.       END;
  290.     END;
  291.     Message('"'+SearchString+'" Not Found.  Press any key');
  292.     while Readkey = #0 do;
  293.   END;
  294.  
  295.  
  296.   PROCEDURE Scroller.AutoScroll;
  297.   Const
  298.     DelayMul = 150;
  299.     Dlay : Integer = 5 * DelayMul;
  300.   Var
  301.     Finished : Boolean;
  302.     ch : char;
  303.     i : integer;
  304.   BEGIN
  305.     Finished := False;
  306.     While Not Finished AND (IxnoY1 < TotalItems-Height) Do BEGIN
  307.       If Keypressed Then BEGIN
  308.     i := pos(ReadKey, '0123456789');
  309.     if i > 0
  310.     Then Dlay := i * DelayMul
  311.     Else Finished := True;
  312.       End Else BEGIN
  313.         ScrollUp;
  314.         ShowStatus;
  315.     Delay(Dlay);
  316.       END;
  317.     END;
  318.   END;
  319.  
  320.   FUNCTION Scroller.ScrollSelect : Char;
  321.   { scroll through file until an invalid key is pressed. }
  322.   VAR
  323.     Ch : Char;
  324.     Finished : Boolean;
  325.   BEGIN
  326.     Finished := False;
  327.     REPEAT
  328.       ShowStatus;
  329.       Ch := ReadKey;
  330.       If Ch = #0 Then BEGIN
  331.         Ch := ReadKey;
  332.     Case Ch OF
  333.       #59  : Help;
  334.       #80 : ScrollUp;
  335.       #72 : ScrollDown;
  336.       #77 : MoveRight(1);
  337.       #75 : MoveLeft(1);
  338.       #115 : MoveLeft(8);
  339.       #116 : MoveRight(8);
  340.       #73 : PgUp;
  341.       #81 : PgDn;
  342.       #71 : TOFL;
  343.       #79 : EOFl;
  344.         ELSE Finished := True;
  345.     END;
  346.       END ELSE CASE UpCase(Ch) OF
  347.     'F','C' : BEGIN
  348.             SearchString := AskString('Search for:');
  349.             CaseSensitive := Ch in ['C','c'];
  350.             IF Not CaseSensitive
  351.             THEN UpCaseString(SearchString);
  352.             SearchForward;
  353.           END;
  354.     'N' : SearchForward;
  355.     'A' : AutoScroll;
  356.         ELSE Finished := True;
  357.       END;
  358.     UNTIL Finished;
  359.     ScrollSelect := Ch;
  360.   END;
  361.  
  362. END.
  363.